package com.miraeasset.www.sitemap;

import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathConstants;
import javax.xml.xpath.XPathExpression;
import javax.xml.xpath.XPathFactory;

import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.xml.sax.SAXException;

public class SiteMapDoc {
	public SiteMapDoc(InputStream docStream) {
		this.docStream = docStream;
		setDocument();
	}
	public List<SiteMapNode> getHistory(String url)
	{
		List<SiteMapNode> ret_sitemapnode_list = new ArrayList<SiteMapNode>();
		Node node = searchNode(url);
		List<Node> ancesstors = getAncesstor(node);
		
		for(int i=ancesstors.size(); i > 0; i--)
		{
			Node item = ancesstors.get(i-1);
			String title = item.getAttributes().getNamedItem("title").getNodeValue();
			String description = item.getAttributes().getNamedItem("description").getNodeValue();
			String link = item.getAttributes().getNamedItem("link").getNodeValue();
			ret_sitemapnode_list.add(new SiteMapNode(title, description, link));
		}
		return ret_sitemapnode_list;
	}

	private InputStream docStream;
	private Document doc = null;

	private void setDocument() {
		DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
		try {
			DocumentBuilder db = dbf.newDocumentBuilder();
			doc = db.parse(docStream);
		} catch (ParserConfigurationException pce) {
			throw new RuntimeException(pce.getMessage());
		} catch (SAXException se) {
			throw new RuntimeException(se.getMessage());
		} catch (IOException ioe) {
			throw new RuntimeException(ioe.getMessage());
		}
	}

	private Node searchNode(String url) {
		XPathFactory fac = XPathFactory.newInstance();
		XPath xpath = fac.newXPath();
		String query = String.format("siteMap//*[@url='%s']", url);
		try {
			XPathExpression expr = xpath.compile(query);
			NodeList nodes = (NodeList)expr.evaluate(doc, XPathConstants.NODESET);
			if(nodes == null) throw new RuntimeException("cannot find url info");
			if (nodes.getLength() > 1) {
				throw new RuntimeException("same url is repeated");
			}
			return nodes.item(0);
		}catch(Exception e){
			throw new RuntimeException(e.getMessage());
		}
	}

	private List<Node> getAncesstor(Node node) {
		List<Node> ancesstor_list = new ArrayList<Node>();
		Node node_ptr = node;
		while (node_ptr != null) {
			if (node_ptr.getParentNode() != null && node_ptr.getParentNode().getParentNode() != null ) {
				ancesstor_list.add(node_ptr);
			}
			node_ptr = node_ptr.getParentNode();
		}
		return ancesstor_list;
	}
}